package com.haiyou.common.util.validate;

import java.util.Iterator;
import java.util.Set;

import javax.validation.ConstraintViolation;
import javax.validation.Validation;
import javax.validation.Validator;

import org.hibernate.validator.HibernateValidator;

import com.haiyou.common.constants.ErrCode;
import com.haiyou.common.util.check.Assert;
import com.haiyou.common.util.string.StringFormatUitls;


/**
 * 
 * 
 * @Description: 主动调用 vaild 注释校验
 * @author xingyuan
 * @date 2022年11月24日 上午11:59:42
 */
public class ValidatorUtils {

	private static Validator validatorFast = Validation.byProvider(HibernateValidator.class).configure().failFast(true).buildValidatorFactory().getValidator();
   
	private static Validator validatorAll = Validation.byProvider(HibernateValidator.class).configure().failFast(false).buildValidatorFactory().getValidator();
    
    /**
     * 校验器
     * @param <T>
     * @param domain
     */
    public static <T> boolean validate(T domain) {
        Set<ConstraintViolation<T>> validateResult = validatorFast.validate(domain);
        if(validateResult.size() <= 0 ) {
        	return true;
        }
        return true;
    }
    
    /**
     * 手动校验
     * @param <T>
     * @param domain
     * @return
     */
    public static <T> void assertValidate(T domain) {
        Set<ConstraintViolation<T>> validateResult = validatorFast.validate(domain);
        String msg = "success";
        if(validateResult.size() > 0 ) {
        	msg = StringFormatUitls.format("Validate Property error {}:{}",validateResult.iterator().next().getPropertyPath(),validateResult.iterator().next().getMessage());
        }
        Assert.isTrue(validateResult.size() <= 0 ,ErrCode.ERROR_PARAMETER,msg);
    }
    
    
    /**
     * 校验遇到第一个不合法的字段直接返回不合法字段，后续字段不再校验
     * @Time 2020年6月22日 上午11:36:13
     * @param <T>
     * @param domain
     * @return
     * @throws Exception
     */
    public static <T> Set<ConstraintViolation<T>> validateFast(T domain) throws Exception {
        Set<ConstraintViolation<T>> validateResult = validatorFast.validate(domain);
        if(validateResult.size()>0) {
            System.out.println(validateResult.iterator().next().getPropertyPath() +"："+ validateResult.iterator().next().getMessage());
        }
        return validateResult;
    }
    
    /**
     * 校验所有字段并返回不合法字段
     * @Time 2020年6月22日 上午11:36:55
     * @param <T>
     * @param domain
     * @return
     * @throws Exception
     */
    public static <T> Set<ConstraintViolation<T>> validateAll(T domain) throws Exception {
        Set<ConstraintViolation<T>> validateResult = validatorAll.validate(domain);
        if(validateResult.size()>0) {
            Iterator<ConstraintViolation<T>> it = validateResult.iterator();
            while(it.hasNext()) {
            	ConstraintViolation<T> cv = it.next();
            	System.out.println(cv.getPropertyPath()+"："+cv.getMessage());
            }
        }
        return validateResult;
    }
    
}
